package org.lansir.af.database;

import android.database.Cursor;
import android.util.Log;

/**
 * 
 * @author 蓝智宏
 * 
 */
public class DataTable {
	private static final String TAG = "DataTable";
	// fields
	private DataRow dataRow = null;
	private long lNewRowId = -1;

	// methods
	public DataTable(DataRow dataRow) {
		this.dataRow = dataRow;
	}

	public Database getUserDb() {
		return dataRow.getUserDb();
	}

	public String getTableName() {
		return dataRow.getTableName();
	}

	public DataRow getDataRow() {
		return dataRow;
	}

	// 创建数据表
	public boolean createTable() {
		if (getUserDb().tableExists(getTableName())) {
			return true;
		} else {
			return getUserDb().execSQL(getSqlTableDefinition(getTableName(), dataRow.getTableDef()));
		}
	}

	// 获得创建创建数据表的sql语句
	public String getSqlTableDefinition(String sTableName, DataField[] vecTableDef) {
		String def = "CREATE TABLE " + sTableName + " (";
		for (int i = 0; i < vecTableDef.length; i++) {
			def += vecTableDef[i].getColumnDefinition();
			if (i < (vecTableDef.length - 1))
				def += ", ";
		}
		def += ")";
		return def;
	}

	public long insertValues() {
		long lRowId = getUserDb().getSQLiteDb().insert(getTableName(), null, dataRow.getContentValues());
		return lRowId;
	}

	public long updateValues(long lRowId) {
		String sWhere = String.format("_ID = %d", lRowId);
		long lRowsUpdated = getUserDb().getSQLiteDb().update(getTableName(), dataRow.getContentValues(), sWhere, null);
		return lRowsUpdated;
	}

	public long updateValuesForParticipator(long lActId, String sPhone) {
		String sWhere = String.format("ActivityID = %d and ParticipatorID='%s'", lActId, sPhone);
		long lRowsUpdated = getUserDb().getSQLiteDb().update(getTableName(), dataRow.getContentValues(), sWhere, null);
		return lRowsUpdated;
	}

	public Cursor locateDataRow(long lRowId) {
		final String s = "select * from %s where _ID = %d";
		String sql = String.format(s, getTableName(), lRowId);
		Cursor cr = getUserDb().getSQLiteDb().rawQuery(sql, null);
		// if cursor valid, set first data row as current
		if ((cr != null) && (cr.getCount() > 0))
			cr.moveToFirst();
		return cr;
	}

	public Cursor locateDataRowByDate(long lStartDate) {
		final String s = "select * from %s where StartDate = %d";
		String sql = String.format(s, getTableName(), lStartDate);
		Cursor cr = getUserDb().getSQLiteDb().rawQuery(sql, null);
		// if cursor valid, set first data row as current
		if ((cr != null) && (cr.getCount() > 0))
			cr.moveToFirst();
		return cr;
	}

	public Cursor locateAlarmDataRow(int iType, long lRefID) {
		final String s = "select * from %s where Type = %d and RefID = %d";
		String sql = String.format(s, getTableName(), iType, lRefID);
		Cursor cr = getUserDb().getSQLiteDb().rawQuery(sql, null);

		// if cursor valid, set first data row as current
		if ((cr != null) && (cr.getCount() > 0))
			cr.moveToFirst();
		else
			cr.close();

		return cr;
	}

	public Database.Result updateData(boolean bInsertMode, long lEditRowId) {
		Database.Result result = Database.Result.errUnknown;
		lNewRowId = lEditRowId;
		if (getUserDb().isOpened()) {
			try {
				dataRow.setValuesForDataRow();
			} catch (Exception e) {
				return Database.Result.errCantSetValuesForDataRow;
			}
			// select update mode
			if (bInsertMode) {
				// insert new data row
				lNewRowId = insertValues();
				if (lNewRowId > 0) {
					result = Database.Result.Success;
				} else {
					result = Database.Result.errCantInsertNewData;
				}
			} else {
				// update existing data row
				long lRowsUpdated = updateValues(lNewRowId);
				if (lRowsUpdated == 1) {
					result = Database.Result.Success;
				} else {
					result = Database.Result.errCantUpdateData;
				}
			}
		} else {
			result = Database.Result.errNoDbAccess;
		}
		return result;
	}

	public long deleteDataRow(long lRowId) {
		String sWhere = String.format("_ID = %d", lRowId);
		long lRowsUpdated = getUserDb().getSQLiteDb().delete(getTableName(), sWhere, null);
		return lRowsUpdated;
	}

	public Database.Result deleteData(long iRowId) {
		Database.Result result = Database.Result.errUnknown;
		if (getUserDb().isOpened()) {
			if (getUserDb().tableExists(getTableName())) {
				long lRowsDeleted = deleteDataRow(iRowId);
				if (lRowsDeleted == 1) {
					result = Database.Result.Success;
				} else {
					result = Database.Result.errCantDeleteData;
				}
			} else {
				result = Database.Result.errTableNotExists;
			}
		} else {
			result = Database.Result.errNoDbAccess;
		}
		return result;
	}

	public Database.Result deleteData(String sWhereClause) {
		Database.Result result = Database.Result.errUnknown;

		if (getUserDb().isOpened()) {
			if (getUserDb().tableExists(getTableName())) {
				getUserDb().getSQLiteDb().delete(getTableName(), sWhereClause, null);
				result = Database.Result.Success;

			} else {
				result = Database.Result.errTableNotExists;
			}
		} else {
			result = Database.Result.errNoDbAccess;
		}

		return result;
	}

	public Database.Result getRowDataForEdit(long lRowId) {
		Database.Result result = Database.Result.errUnknown;
		// get requested data row
		Cursor cr = locateDataRow(lRowId);
		if (cr == null) {
			result = Database.Result.errCantGetData;
		} else {
			try {
				if (cr.getCount() > 0) {
					if (dataRow.getValuesFromCursor(cr)) {

						dataRow.getValuesFromDataRow();

						result = Database.Result.Success;
					} else {
						result = Database.Result.errCantGetDataFromTable;
					}
				} else {
					result = Database.Result.errCantFindData;
				}
			} catch (Exception e) {
				return Database.Result.errCantGetValuesFromDataRow;
			} finally {
				cr.close();
			}
		}
		return result;
	}

	public Cursor locateDataRow(String sWhereClause) {
		final String s = "select * from %s where " + sWhereClause;
		String sql = String.format(s, getTableName());
		Log.v(TAG, "sql : " + sql);
		Cursor cr = null;
		try{
			cr = getUserDb().getSQLiteDb().rawQuery(sql, null);
			// if cursor valid, set first data row as current
			if ((cr != null) && (cr.getCount() > 0))
				cr.moveToFirst();
			
		}catch(Exception ex){
			ex.printStackTrace();
			return null;
		}
		return cr;
		
	}

	public Database.Result getRowDataForEdit(String sWhereClause) {
		Database.Result result = Database.Result.errUnknown;
		// get requested data row
		Log.v(TAG, "before locateDataRow");
		Cursor cr = locateDataRow(sWhereClause);
		Log.v(TAG, "after locateDataRow:cr==null:" + (cr==null));
		if (cr == null) {
			result = Database.Result.errCantGetData;
		} else {
			try {
				if (cr.getCount() > 0) {
					if (dataRow.getValuesFromCursor(cr)) {

						dataRow.getValuesFromDataRow();

						result = Database.Result.Success;
					} else {
						result = Database.Result.errCantGetDataFromTable;
					}
				} else {
					Log.v(TAG, "errCantFindData");
					result = Database.Result.errCantFindData;
				}

			} catch (Exception e) {
				e.printStackTrace();
				return Database.Result.errCantGetValuesFromDataRow;
			} finally {
				cr.close();
			}
		}
		return result;
	}

	public Database.Result getRowDataForEditByDay(int lStartDay) {
		Database.Result result = Database.Result.errUnknown;
		// get requested data row
		Cursor cr = locateDataRow(lStartDay);
		if (cr == null) {
			result = Database.Result.errCantGetData;
		} else {
			try {
				if (cr.getCount() > 0) {
					if (dataRow.getValuesFromCursor(cr)) {

						dataRow.getValuesFromDataRow();

						result = Database.Result.Success;
					} else {
						result = Database.Result.errCantGetDataFromTable;
					}

				} else {
					result = Database.Result.errCantFindData;
				}
			} catch (Exception e) {
				return Database.Result.errCantGetValuesFromDataRow;
			} finally {
				cr.close();
			}
		}
		return result;
	}

	public long getNewRowId() {
		return lNewRowId;
	}

	public void setNewRowId(long newRowId) {
		lNewRowId = newRowId;
	}

}
